home *** CD-ROM | disk | FTP | other *** search
/ Personal Computer World 2008 February / PCWFEB08.iso / Software / Freeware / Miro 1.0 / Miro_Installer.exe / Miro_Downloader.exe / tabs.pyc (.txt) < prev    next >
Encoding:
Python Compiled Bytecode  |  2007-11-12  |  13.7 KB  |  426 lines

  1. # Source Generated with Decompyle++
  2. # File: in.pyc (Python 2.5)
  3.  
  4. import database
  5. import app
  6. import template
  7. import views
  8. import eventloop
  9. import feed
  10. import folder
  11. import resources
  12. import guide
  13. import playlist
  14. import sorts
  15. from util import checkU, getSingletonDDBObject
  16. from databasehelper import TrackedIDList
  17. from xml.dom.minidom import parse
  18. from gtcache import gettext as _
  19. import logging
  20.  
  21. class StaticTab(database.DDBObject):
  22.     tabTitles = {
  23.         'librarytab': _('Library'),
  24.         'newtab': _('New'),
  25.         'searchtab': _('Video Search'),
  26.         'downloadtab': _('Downloading') }
  27.     tabIcons = {
  28.         'librarytab': 'collection-icon-tablist.png',
  29.         'newtab': 'newvideos-icon-tablist.png',
  30.         'searchtab': 'search-icon-tablist.png',
  31.         'downloadtab': 'download-icon-tab.png' }
  32.     
  33.     def __init__(self, tabTemplateBase, contentsTemplate, state, order):
  34.         self.tabTemplateBase = tabTemplateBase
  35.         self.contentsTemplate = contentsTemplate
  36.         self.order = order
  37.         self.templateState = state
  38.         database.DDBObject.__init__(self)
  39.  
  40.     
  41.     def getTitle(self):
  42.         return self.tabTitles[self.tabTemplateBase]
  43.  
  44.     
  45.     def getIconURL(self):
  46.         return resources.url('images/%s' % self.tabIcons[self.tabTemplateBase])
  47.  
  48.     
  49.     def getNumberColor(self):
  50.         if self.tabTemplateBase == 'downloadtab':
  51.             return 'orange'
  52.         elif self.tabTemplateBase == 'newtab':
  53.             return 'green'
  54.         else:
  55.             return None
  56.  
  57.     
  58.     def getNumber(self):
  59.         if self.tabTemplateBase == 'downloadtab':
  60.             return views.downloadingItems.len()
  61.         elif self.tabTemplateBase == 'newtab':
  62.             return views.unwatchedItems.len()
  63.         else:
  64.             return 0
  65.  
  66.     
  67.     def enableNewVideoPlayButton(self):
  68.         if self.tabTemplateBase == 'newtab':
  69.             pass
  70.         return views.unwatchedItems.len() > 0
  71.  
  72.  
  73.  
  74. class Tab:
  75.     idCounter = 0
  76.     
  77.     def __init__(self, tabTemplateBase, contentsTemplate, templateState, obj):
  78.         self.tabTemplateBase = tabTemplateBase
  79.         self.contentsTemplate = contentsTemplate
  80.         self.templateState = templateState
  81.         self.display = None
  82.         self.id = 'tab%d' % Tab.idCounter
  83.         Tab.idCounter += 1
  84.         self.selected = False
  85.         self.active = False
  86.         self.obj = obj
  87.         if obj.__class__ == guide.ChannelGuide:
  88.             self.type = 'guide'
  89.         elif obj.__class__ == StaticTab:
  90.             self.type = 'statictab'
  91.         elif obj.__class__ in (feed.Feed, folder.ChannelFolder):
  92.             self.type = 'feed'
  93.         elif obj.__class__ in (playlist.SavedPlaylist, folder.PlaylistFolder):
  94.             self.type = 'playlist'
  95.         else:
  96.             raise TypeError('Bad tab object type: %s' % type(obj))
  97.  
  98.     
  99.     def getDragSourceType(self):
  100.         selection = app.controller.selection.tabListSelection
  101.         if self.type == 'feed':
  102.             if (isinstance(self.obj, folder.ChannelFolder) or self.selected) and selection.isFolderSelected():
  103.                 return 'channelfolder'
  104.             else:
  105.                 return 'channel'
  106.         elif self.type == 'playlist':
  107.             if (isinstance(self.obj, folder.PlaylistFolder) or self.selected) and selection.isFolderSelected():
  108.                 return 'playlistfolder'
  109.             else:
  110.                 return 'playlist'
  111.         else:
  112.             return ''
  113.  
  114.     
  115.     def setActive(self, newValue):
  116.         self.obj.confirmDBThread()
  117.         self.active = newValue
  118.         self.obj.signalChange(needsSave = False)
  119.  
  120.     
  121.     def setSelected(self, newValue):
  122.         self.obj.confirmDBThread()
  123.         self.selected = newValue
  124.         self.obj.signalChange(needsSave = False)
  125.  
  126.     
  127.     def getSelected(self):
  128.         self.obj.confirmDBThread()
  129.         return self.selected
  130.  
  131.     
  132.     def getActive(self):
  133.         self.obj.confirmDBThread()
  134.         return self.active
  135.  
  136.     
  137.     def getState(self):
  138.         if not self.selected:
  139.             return 'normal'
  140.         elif not self.active:
  141.             return 'selected-inactive'
  142.         else:
  143.             return 'selected'
  144.  
  145.     
  146.     def redraw(self):
  147.         self.obj.signalChange()
  148.  
  149.     
  150.     def isStatic(self):
  151.         '''True if this Tab represents a StaticTab.'''
  152.         return isinstance(self.obj, StaticTab)
  153.  
  154.     
  155.     def isFeed(self):
  156.         '''True if this Tab represents a Feed.'''
  157.         return isinstance(self.obj, feed.Feed)
  158.  
  159.     
  160.     def isChannelFolder(self):
  161.         '''True if this Tab represents a Channel Folder.'''
  162.         return isinstance(self.obj, folder.ChannelFolder)
  163.  
  164.     
  165.     def isGuide(self):
  166.         '''True if this Tab represents a Channel Guide.'''
  167.         return isinstance(self.obj, guide.ChannelGuide)
  168.  
  169.     
  170.     def isPlaylist(self):
  171.         '''True if this Tab represents a Playlist.'''
  172.         return isinstance(self.obj, playlist.SavedPlaylist)
  173.  
  174.     
  175.     def isPlaylistFolder(self):
  176.         '''True if this Tab represents a Playlist Folder.'''
  177.         return isinstance(self.obj, folder.PlaylistFolder)
  178.  
  179.     
  180.     def feedURL(self):
  181.         '''If this Tab represents a Feed or a Guide, the URL. Otherwise None.'''
  182.         if self.isFeed() or self.isGuide():
  183.             return self.obj.getURL()
  184.         else:
  185.             return None
  186.  
  187.     
  188.     def objID(self):
  189.         """If this Tab represents a Feed, the feed's ID. Otherwise None."""
  190.         if isinstance(self.obj, database.DDBObject):
  191.             return self.obj.getID()
  192.         else:
  193.             return None
  194.  
  195.     
  196.     def getID(self):
  197.         """Gets an id that can be used to lookup this tab from views.allTabs.
  198.  
  199.         NOTE: Tabs are mapped database objects, they don't have actual
  200.         DDBObject ids.
  201.         """
  202.         return self.obj.getID()
  203.  
  204.     
  205.     def signalChange(self, needsSave = True):
  206.         '''Call signalChange on the object that is mapped to this tab (the
  207.         StaticTab, Feed, Playlist, etc.)
  208.         '''
  209.         self.obj.signalChange(needsSave = needsSave)
  210.  
  211.     
  212.     def idExists(self):
  213.         '''Returns True if the object that maps to this tab still exists in
  214.         the DB.
  215.         '''
  216.         return self.obj.idExists()
  217.  
  218.     
  219.     def onDeselected(self, frame):
  220.         self.display.onDeselect(frame)
  221.  
  222.     
  223.     def getFragment(self):
  224.         '''URL fragment to use as an anchor.  This lets us scroll the tablist
  225.         so that this tab is on top.
  226.         '''
  227.         return 'tab-%d' % self.obj.getID()
  228.  
  229.  
  230.  
  231. def expandedFolderFilter(tab):
  232.     folder = tab.obj.getFolder()
  233.     if not folder is None:
  234.         pass
  235.     return folder.getExpanded()
  236.  
  237.  
  238. class TabOrder(database.DDBObject):
  239.     '''TabOrder objects keep track of the order of the tabs.  Democracy
  240.     creates 2 of these, one to track channels/channel folders and another to
  241.     track playlists/playlist folders.
  242.     '''
  243.     
  244.     def __init__(self, type):
  245.         '''Construct a TabOrder.  type should be either "channel", or
  246.         "playlist".
  247.         '''
  248.         checkU(type)
  249.         self.type = type
  250.         self.tab_ids = []
  251.         self._initRestore()
  252.         decorated = [ (t.obj.getTitle().lower(), t) for t in self.tabView ]
  253.         decorated.sort()
  254.         for sortkey, tab in decorated:
  255.             self.trackedTabs.appendID(tab.getID())
  256.         
  257.         database.DDBObject.__init__(self)
  258.  
  259.     
  260.     def onRestore(self):
  261.         self._initRestore()
  262.         eventloop.addIdle(self.checkForNonExistentIds, 'checking for non-existent TabOrder ids')
  263.  
  264.     
  265.     def _initRestore(self):
  266.         if self.type == u'channel':
  267.             self.tabView = views.feedTabs
  268.         elif self.type == u'playlist':
  269.             self.tabView = views.playlistTabs
  270.         else:
  271.             raise ValueError('Bad type for TabOrder')
  272.         self.trackedTabs = TrackedIDList(self.tabView, self.tab_ids)
  273.         self.trackedTabs.setFilter(expandedFolderFilter)
  274.         self.tabView.addAddCallback(self.onAddTab)
  275.         self.tabView.addRemoveCallback(self.onRemoveTab)
  276.  
  277.     
  278.     def checkForNonExistentIds(self):
  279.         changed = False
  280.         for id in self.tab_ids[:]:
  281.             if not self.tabView.idExists(id):
  282.                 self.trackedTabs.removeID(id)
  283.                 logging.warn('Throwing away non-existent TabOrder id: %s', id)
  284.                 changed = True
  285.                 continue
  286.         
  287.         if changed:
  288.             self.signalChange()
  289.         
  290.  
  291.     
  292.     def makeLastTabVisible(self, obj):
  293.         
  294.         try:
  295.             tabDisplay = app.controller.tabDisplay
  296.         except AttributeError:
  297.             return None
  298.  
  299.         tabToShow = obj
  300.         self.trackedTabs.view.moveCursorToID(obj.objID())
  301.         for i in range(3):
  302.             last = self.trackedTabs.view.getPrev()
  303.             if last is None:
  304.                 break
  305.             
  306.             tabToShow = last
  307.         
  308.         if hasattr(tabDisplay, 'navigateToFragment'):
  309.             tabDisplay.navigateToFragment(tabToShow.getFragment())
  310.         else:
  311.             logging.warn('HTMLDisplay.navigateToFragment not implemented')
  312.  
  313.     
  314.     def getView(self):
  315.         '''Get a database view for this tab ordering.'''
  316.         return self.trackedTabs.view
  317.  
  318.     
  319.     def getAllTabs(self):
  320.         '''Get all the tabs in this tab ordering (in order), regardless if
  321.         they are visible in the tab list or not.
  322.         '''
  323.         return _[1]
  324.  
  325.     
  326.     def onAddTab(self, obj, id):
  327.         if id not in self.trackedTabs:
  328.             self.trackedTabs.appendID(id, sendSignalChange = False)
  329.             obj.signalChange(needsSave = False)
  330.             self.signalChange()
  331.             self.makeLastTabVisible(obj)
  332.         
  333.  
  334.     
  335.     def onRemoveTab(self, obj, id):
  336.         if id in self.trackedTabs:
  337.             self.trackedTabs.removeID(id)
  338.         
  339.         self.signalChange()
  340.  
  341.     
  342.     def handleDNDReorder(self, anchorItem, draggedIDs):
  343.         '''Handle drag-and-drop reordering of the tab order.'''
  344.         for iid in draggedIDs:
  345.             if iid not in self.trackedTabs:
  346.                 raise ValueError('ID not in TabOrder: %s', iid)
  347.                 continue
  348.         
  349.         if anchorItem is None:
  350.             newFolder = None
  351.         else:
  352.             newFolder = anchorItem.getFolder()
  353.         childrenIDs = set()
  354.         for id in draggedIDs:
  355.             tab = self.trackedTabs.view.getObjectByID(id)
  356.             tab.obj.setFolder(newFolder)
  357.             if isinstance(tab.obj, folder.FolderBase):
  358.                 for child in tab.obj.getChildrenView():
  359.                     childrenIDs.add(child.getID())
  360.                 
  361.         
  362.         toMove = draggedIDs.union(childrenIDs)
  363.         self.moveTabs(anchorItem, toMove, sendSignalChange = False)
  364.         self.signalChange()
  365.  
  366.     
  367.     def moveTabs(self, anchorItem, toMove, sendSignalChange = True):
  368.         if anchorItem is not None:
  369.             self.trackedTabs.moveIDList(toMove, anchorItem.getID())
  370.         else:
  371.             self.trackedTabs.moveIDList(toMove, None)
  372.         if sendSignalChange:
  373.             self.signalChange()
  374.         
  375.  
  376.  
  377.  
  378. def removeStaticTabs():
  379.     app.db.confirmDBThread()
  380.     for obj in views.staticTabsObjects:
  381.         obj.remove()
  382.     
  383.  
  384.  
  385. def reloadStaticTabs():
  386.     app.db.confirmDBThread()
  387.     removeStaticTabs()
  388.     document = parse(resources.path('statictabs.xml'))
  389.     for n in document.getElementsByTagName('statictab'):
  390.         tabTemplateBase = n.getAttribute('tabtemplatebase')
  391.         contentsTemplate = n.getAttribute('contentstemplate')
  392.         state = n.getAttribute('state')
  393.         order = int(n.getAttribute('order'))
  394.         StaticTab(tabTemplateBase, contentsTemplate, state, order)
  395.     
  396.  
  397.  
  398. def tabIterator():
  399.     '''Iterates over all tabs in order'''
  400.     for tab in views.guideTabs:
  401.         yield tab
  402.     
  403.     for tab in views.staticTabs:
  404.         yield tab
  405.     
  406.     for tab in getSingletonDDBObject(views.channelTabOrder).getView():
  407.         yield tab
  408.     
  409.     for tab in getSingletonDDBObject(views.playlistTabOrder).getView():
  410.         yield tab
  411.     
  412.  
  413.  
  414. def getViewForTab(tab):
  415.     if tab.type == 'guide':
  416.         return views.guideTabs
  417.     elif tab.type == 'statictab':
  418.         return views.staticTabs
  419.     elif tab.type == 'feed':
  420.         return getSingletonDDBObject(views.channelTabOrder).getView()
  421.     elif tab.type == 'playlist':
  422.         return getSingletonDDBObject(views.playlistTabOrder).getView()
  423.     
  424.     raise AssertionError('Unknown tab type')
  425.  
  426.